package com.hxh.component.business.ui;

import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Matrix;
import android.os.Environment;
import android.view.View;

import com.hxh.component.basicore.Base.app.AppManager;
import com.hxh.component.basicore.util.Utils;
import com.hxh.component.basicore.util.convert.JsonFactory;
import com.hxh.component.business.R;
import com.hxh.component.common.PickerStyle;
import com.hxh.component.common.listener.OnPickViewListener;
import com.hxh.component.common.model.OneLevel_Bean;
import com.hxh.component.common.model.TwoLevel_Bean;
import com.hxh.component.pickerview.ui.picker.PickerView;
import com.hxh.component.ui.alertview.AlertView;
import com.hxh.component.ui.alertview.OnItemClickListener;

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.Serializable;
import java.lang.reflect.Field;
import java.lang.reflect.Modifier;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.AbstractList;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.Collection;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.RandomAccess;

import cn.qqtheme.framework.entity.Province;
import cn.qqtheme.framework.picker.AddressPicker;
import cn.qqtheme.framework.picker.DoublePicker;
import cn.qqtheme.framework.picker.OptionPicker;
import cn.qqtheme.framework.picker.WheelPicker;

import static com.hxh.component.basicore.util.Utils.Regx.validation;

/**
 * Created by mardawang on 2018/1/20.
 */

public class MyUtil { private static Context mContext;
    private static final String SDPATH = Environment.getExternalStorageDirectory().getAbsolutePath()+"/DCIM/workai/";

    public static void init(Context context) {
        mContext = context;

    }

    public static Context getApplicationContext() {
        if (null == mContext) {
            throw new IllegalStateException("you first call Utils.init()...");
        }
        return mContext;
    }

    public static class BitmapUtils {

        public static Bitmap getSmallBitmap(String filePath) {
            final BitmapFactory.Options options = new BitmapFactory.Options();
            options.inJustDecodeBounds = true;
            BitmapFactory.decodeFile(filePath, options);

            // Calculate inSampleSize
            options.inSampleSize = calculateInSampleSize(options, 480, 800);

            // Decode bitmap with inSampleSize set
            options.inJustDecodeBounds = false;

            return BitmapFactory.decodeFile(filePath, options);
        }

        public static int calculateInSampleSize(BitmapFactory.Options options, int reqWidth,
                                                int reqHeight) {
            // Raw height and width of image
            final int height = options.outHeight;
            final int width = options.outWidth;
            int inSampleSize = 1;

            if (height > reqHeight || width > reqWidth) {

                // Calculate ratios of height and width to requested height and
                // width
                final int heightRatio = Math.round((float) height / (float) reqHeight);
                final int widthRatio = Math.round((float) width / (float) reqWidth);

                inSampleSize = heightRatio < widthRatio ? heightRatio : widthRatio;
            }

            return inSampleSize;
        }

        public static Bitmap getSmallBitmap(Bitmap image) {

            ByteArrayOutputStream baos = new ByteArrayOutputStream();
            image.compress(Bitmap.CompressFormat.JPEG, 100, baos);
            if (baos.toByteArray().length / 1024 > 1024) {//判断如果图片大于1M,进行压缩避免在生成图片（BitmapFactory.decodeStream）时溢出
                baos.reset();//重置baos即清空baos
                image.compress(Bitmap.CompressFormat.JPEG, 50, baos);//这里压缩50%，把压缩后的数据存放到baos中
            }
            ByteArrayInputStream isBm = new ByteArrayInputStream(baos.toByteArray());
            BitmapFactory.Options newOpts = new BitmapFactory.Options();
            //开始读入图片，此时把options.inJustDecodeBounds 设回true了
            newOpts.inJustDecodeBounds = true;
            Bitmap bitmap = BitmapFactory.decodeStream(isBm, null, newOpts);
            newOpts.inJustDecodeBounds = false;
            int w = newOpts.outWidth;
            int h = newOpts.outHeight;
            //现在主流手机比较多是800*480分辨率，所以高和宽我们设置为
            float hh = 800f;//这里设置高度为800f
            float ww = 480f;//这里设置宽度为480f
            //缩放比。由于是固定比例缩放，只用高或者宽其中一个数据进行计算即可
            int be = 1;//be=1表示不缩放
            if (w > h && w > ww) {//如果宽度大的话根据宽度固定大小缩放
                be = (int) (newOpts.outWidth / ww);
            } else if (w < h && h > hh) {//如果高度高的话根据宽度固定大小缩放
                be = (int) (newOpts.outHeight / hh);
            }
            if (be <= 0)
                be = 1;
            newOpts.inSampleSize = be;//设置缩放比例
            //重新读入图片，注意此时已经把options.inJustDecodeBounds 设回false了
            isBm = new ByteArrayInputStream(baos.toByteArray());
            bitmap = BitmapFactory.decodeStream(isBm, null, newOpts);
            return bitmap;//压缩好比例大小后再进行质量压缩
        }

        public static Bitmap getResizeBitmap(String imageFilePath, int targetValue) {
            int targetWidth;
            int targetHeight;
            Bitmap bitmap = BitmapFactory.decodeFile(imageFilePath);

            if (bitmap.getWidth() > bitmap.getHeight()) {
                targetWidth = targetValue;
//                targetHeight = bitmap.getHeight() / bitmap.getWidth() * targetWidth;
                targetHeight = (targetWidth * bitmap.getHeight()) / bitmap.getWidth();
            } else {
                targetHeight = targetValue;
                targetWidth = (targetHeight * bitmap.getWidth()) / bitmap.getHeight();
            }

            return Bitmap.createScaledBitmap(bitmap, targetWidth, targetHeight, true);
        }

        // 将生成的图片保存到本地
        public static String saveBitmap(Bitmap bitmap, String name) {
            File file;
            String savePath;

            if (Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED)) {
                savePath = SDPATH;
            } else {
                savePath = getApplicationContext().getFilesDir()
                        .getAbsolutePath()
                        + "/workai/";
            }
            try {
                file = new File(savePath + name + ".jpg");
                if (!file.exists()) {
                    file.getParentFile().mkdirs();
                    file.createNewFile();
                }
                FileOutputStream fos = new FileOutputStream(file);
                bitmap.compress(Bitmap.CompressFormat.PNG, 100, fos);
                fos.flush();
                fos.close();
            } catch (IOException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
                return null;
            }

            return file.getAbsolutePath();
        }

        //将bitmap调整到指定大小
        public static Bitmap resizeBitmap(Bitmap origin, int newWidth, int newHeight) {
            if (origin == null) {
                return null;
            }
            int height = origin.getHeight();
            int width = origin.getWidth();
            float scaleWidth = ((float) newWidth) / width;
            float scaleHeight = ((float) newHeight) / height;
            Matrix matrix = new Matrix();
            matrix.postScale(scaleWidth, scaleHeight);// 使用后乘
            Bitmap newBM = Bitmap.createBitmap(origin, 0, 0, width, height, matrix, false);
            if (!origin.isRecycled()) {//这时候origin还有吗？
                origin.recycle();
            }
            return newBM;
        }

    }


    public static class CollectionsUtil {

        private static final Collection NULL_COLLECTION = new Utils.CollectionsUtil.NullCollection();

        private static final String SEP1 = ",";
        private static final String SEP2 = "|";
        private static final String SEP3 = "=";

        public static final <T> Collection<T> nullCollection() {
            return (List<T>) NULL_COLLECTION;
        }

        public static class NullCollection extends AbstractList<Object>
                implements RandomAccess, Serializable {

            private static final long serialVersionUID = 5206887786441397812L;

            @Override
            public Object get(int index) {
                return null;
            }

            @Override
            public int size() {
                return 1;
            }

            public boolean contains(Object obj) {
                return null == obj;
            }

            private Object readResolve() {
                return null;
            }
        }


        /**
         * List转换String
         *
         * @param list
         *            :需要转换的List
         * @return String转换后的字符串
         */
        public static String ListToString(List<?> list) {
            StringBuffer sb = new StringBuffer();
            if (list != null && list.size() > 0) {
                for (int i = 0; i < list.size(); i++) {
                    if (list.get(i) == null || list.get(i) == "") {
                        continue;
                    }
                    // 如果值是list类型则调用自己
                    if (list.get(i) instanceof List) {
                        sb.append(ListToString((List<?>) list.get(i)));
                        sb.append(SEP1);
                    } else if (list.get(i) instanceof Map) {
                        sb.append(MapToString((Map<?, ?>) list.get(i)));
                        sb.append(SEP1);
                    } else {
                        sb.append(list.get(i));
                        sb.append(SEP1);
                    }
                }
            }
            return "L" + sb.toString();
        }

        /**
         * Map转换String
         *
         * @param map
         *            :需要转换的Map
         * @return String转换后的字符串
         */
        public static String MapToString(Map<?, ?> map) {
            StringBuffer sb = new StringBuffer();
            // 遍历map
            for (Object obj : map.keySet()) {
                if (obj == null) {
                    continue;
                }
                Object key = obj;
                Object value = map.get(key);
                if (value instanceof List<?>) {
                    sb.append(key.toString() + SEP1 + ListToString((List<?>) value));
                    sb.append(SEP2);
                } else if (value instanceof Map<?, ?>) {
                    sb.append(key.toString() + SEP1 + MapToString((Map<?, ?>) value));
                    sb.append(SEP2);
                } else {
                    sb.append(key.toString() + SEP3 + value.toString());
                    sb.append(SEP2);
                }
            }
            return "M" + sb.toString();
        }

        /**
         * String转换Map
         *
         * @param mapText
         *            :需要转换的字符串
         * @return Map<?,?>
         */
        public static Map<String, Object> StringToMap(String mapText) {

            if (mapText == null || mapText.equals("")) {
                return null;
            }
            mapText = mapText.substring(1);

            Map<String, Object> map = new HashMap<String, Object>();
            String[] text = mapText.split("\\" + SEP2); // 转换为数组
            for (String str : text) {
                String[] keyText = str.split(SEP3); // 转换key与value的数组
                if (keyText.length < 1) {
                    continue;
                }
                String key = keyText[0]; // key
                String value = keyText[1]; // value
                if (value.charAt(0) == 'M') {
                    Map<?, ?> map1 = StringToMap(value);
                    map.put(key, map1);
                } else if (value.charAt(0) == 'L') {
                    List<?> list = StringToList(value);
                    map.put(key, list);
                } else {
                    map.put(key, value);
                }
            }
            return map;
        }

        /**
         * String转换List
         *
         * @param listText
         *            :需要转换的文本
         * @return List<?>
         */
        public static List<Object> StringToList(String listText) {
            if (listText == null || listText.equals("")) {
                return null;
            }
            listText = listText.substring(1);

            List<Object> list = new ArrayList<Object>();
            String[] text = listText.split("\\" + SEP1);
            String listStr = "";
            boolean flag = false;
            for (String str : text) {
                if (!str.equals("")) {
                    if (str.charAt(0) == 'M') {
                        Map<?, ?> map = StringToMap(str);
                        list.add(map);
                    } else if (str.charAt(0) == 'L' || flag) {
                        flag = true;
                        listStr += str + SEP1;
                    } else {
                        list.add(str);
                    }
                }
                if (str.equals("")) {
                    flag = false;
                    List<?> lists = StringToList(listStr);
                    list.add(lists);
                }
            }
            return list;
        }

        /**
         * 将对象装换为map
         *
         * @param
         * @param
         * @return
         */
        public static HashMap<String, Object> objToHashMap(Object obj) {
            try {
                HashMap<String, Object> hashMap = new HashMap<String, Object>();
                Class clazz = obj.getClass();
                List<Class> clazzs = new ArrayList<Class>();

                do {
                    clazzs.add(clazz);
                    clazz = clazz.getSuperclass();
                } while (!clazz.equals(Object.class));

                for (Class iClazz : clazzs) {
                    Field[] fields = iClazz.getDeclaredFields();
                    for (Field field : fields) {
                        Object objVal = null;
                        field.setAccessible(true);
                        objVal = field.get(obj);
                        hashMap.put(field.getName(), objVal);
                    }
                }
                return hashMap;
            } catch (Exception e) {

            }
            return null;
        }

        public static Object mapToObject(Map<String, Object> map, Class<?> beanClass) throws Exception {
            if (map == null)
                return null;

            Object obj = beanClass.newInstance();

            Field[] fields = obj.getClass().getDeclaredFields();
            for (Field field : fields) {
                int mod = field.getModifiers();
                if (Modifier.isStatic(mod) || Modifier.isFinal(mod)) {
                    continue;
                }

                field.setAccessible(true);
                field.set(obj, map.get(field.getName()));
            }

            return obj;
        }

    }

    public static class Time{

        public static int getDaysFromdate(long s1,long s2) {
            int days = 0;
            try {
                //时间转换类
                SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");

                Date date1 = sdf.parse(sdf.format(s1));
                Date date2 = sdf.parse(sdf.format(s2));
                //将转换的两个时间对象转换成Calendard对象
                Calendar can1 = Calendar.getInstance();
                can1.setTime(date1);
                Calendar can2 = Calendar.getInstance();
                can2.setTime(date2);
                //拿出两个年份
                int year1 = can1.get(Calendar.YEAR);
                int year2 = can2.get(Calendar.YEAR);
                //天数

                Calendar can = null;
                //如果can1 < can2
                //减去小的时间在这一年已经过了的天数
                //加上大的时间已过的天数
                if (can1.before(can2)) {
                    days -= can1.get(Calendar.DAY_OF_YEAR);
                    days += can2.get(Calendar.DAY_OF_YEAR);
                    can = can1;
                } else {
                    days -= can2.get(Calendar.DAY_OF_YEAR);
                    days += can1.get(Calendar.DAY_OF_YEAR);
                    can = can2;
                }
                for (int i = 0; i < Math.abs(year2 - year1); i++) {
                    //获取小的时间当前年的总天数
                    days += can.getActualMaximum(Calendar.DAY_OF_YEAR);
                    //再计算下一年。
                    can.add(Calendar.YEAR, 1);
                }
            } catch (ParseException e) {
                e.printStackTrace();
            }
            return days;
        }

        //根据传入的小时数 获取当前的时间戳（单位：秒）
        public static long getMillionsByHour(float h){
            long mill_seconds = 0;
            mill_seconds = (long) (h*60*60);
            return mill_seconds;
        }

    }

    public static class SystemUtil{

        public static int getStatusHeight(Context context){
            int statusBarHeight = -1;
            //获取status_bar_height资源的ID
            int resourceId = context.getResources().getIdentifier("status_bar_height", "dimen", "android");
            if (resourceId > 0) {
                //根据资源ID获取响应的尺寸值
                statusBarHeight = context.getResources().getDimensionPixelSize(resourceId);
            }
            return statusBarHeight;
        }

    }

    public static class DialogUtils {


        public static AlertView showDeleteDialog(String msg, OnItemClickListener lis) {

            return showDefaulStyleDialog(null, Utils.Text.isEmpty(msg) ? "确认删除吗？" : msg, "取消", "确认",null, AlertView.Style.Alert, lis,true);
        }

        public static AlertView showDefaulStyleDialog(View view,boolean isCanceble)
        {
            AlertView al = new AlertView(view);
            al.setCancelable(isCanceble);
            return al;
        }

        /**
         * @param message   提示的文本
         * @param cancel    返回的文本
         * @param determine 确定的文本
         * @param lis       按钮监听
         * @return
         */
        public static AlertView showDefaulStyleDialog(String message, String cancel, String determine, OnItemClickListener lis) {
            return showDefaulStyleDialog(null, message, cancel, determine,null, AlertView.Style.Alert, lis,true);
        }

        public static AlertView showDefaulStyleDialog(String message, String cancel, String determine,boolean cancleable, OnItemClickListener lis) {
            return showDefaulStyleDialog(null, message, cancel, determine,null, AlertView.Style.Alert, lis,cancleable);
        }

        public static AlertView showDefaulStyleDialog(String title,String message, String cancel, String determine,boolean cancleable, OnItemClickListener lis) {
            return showDefaulStyleDialog(title, message, cancel, determine,null, AlertView.Style.Alert, lis,cancleable);
        }

        public static AlertView showDefaulStyleDialog(String[] other, OnItemClickListener lis) {
            return showDefaulStyleDialog(null, null, "返回",null,other, AlertView.Style.ActionSheet, lis,true);
        }
        public static AlertView showDefaulStyleDialog(String title,String[] other, OnItemClickListener lis) {
            return showDefaulStyleDialog(title, null, "返回",null,other, AlertView.Style.ActionSheet, lis,true);
        }
        public static AlertView showDefaulStyleDialog(String message,String cancel,String[] other, OnItemClickListener lis) {
            return showDefaulStyleDialog(null, message, cancel,null,other, AlertView.Style.ActionSheet, lis,true);
        }


        public static AlertView showDefaulStyleDialog(String message, OnItemClickListener lis) {
            return showDefaulStyleDialog(null, message, "返回", "确定",null, AlertView.Style.Alert, lis,true);
        }
        public static AlertView showDefaulStyleDialog(String message,boolean iscanceable, OnItemClickListener lis) {
            return showDefaulStyleDialog(null, message, "返回", "确定", null, AlertView.Style.Alert,lis,iscanceable);
        }

        public static AlertView showDefaulStyleDialog(String message, String determine, OnItemClickListener lis) {
            return showDefaulStyleDialog(null, message, null, determine,null, AlertView.Style.Alert, lis,true);
        }


        public static AlertView showDefaulStyleDialog(String title, String message, String cancel, String determine, String[]others, AlertView.Style style,OnItemClickListener lis, boolean iscanceable) {
            AlertView.Builder builder = new AlertView.Builder(AppManager.getCurrentActivity())
                    .setTitle(title)
                    .setMessage(message)
                    .setCancelText(cancel)
                    .setConfirmText(determine)
                    .setOthers(others)
                    .setOnItemClickListenerTest(lis);
            if(style == AlertView.Style.Alert)
            {
                builder.setStyle( AlertView.Style.Alert);
            }else
            {
                builder.setStyle( AlertView.Style.ActionSheet);
            }


            return  builder.build().setCancelable(iscanceable);
        }

        /**
         *
         * @param context
         * @param startHour  从哪个小时开始
         * @param startMin   从多少分开始   目前暂定 00和30
         * @param listener
         */
        public static void showTimePickerDialog(Context context,int startHour,String startMin,OnPickViewListener listener) {

            String hourJson = "[{\"name\":\"0\"},{\"name\":\"1\"},{\"name\":\"2\"},{\"name\":\"3\"},{\"name\":\"4\"},{\"name\":\"5\"},{\"name\":\"6\"},{\"name\":\"7\"},{\"name\":\"8\"},{\"name\":\"9\"},{\"name\":\"10\"},{\"name\":\"11\"},{\"name\":\"12\"},{\"name\":\"13\"},{\"name\":\"14\"},{\"name\":\"15\"},{\"name\":\"16\"},{\"name\":\"17\"},{\"name\":\"18\"},{\"name\":\"19\"},{\"name\":\"20\"},{\"name\":\"21\"},{\"name\":\"22\"},{\"name\":\"23\"}]";
            ArrayList<OneLevel_Bean> oneLevel_beens = (ArrayList<OneLevel_Bean>) JsonFactory.getFastJsonConvert().toArray(hourJson,OneLevel_Bean.class);
            if(-1 != startHour)
            {
                for (int i = 0; i < startHour; i++) {
                    oneLevel_beens.set(i,null);
                }
                //移除null
                oneLevel_beens.removeAll(com.hxh.component.basicore.util.Utils.CollectionsUtil.nullCollection());
            }
            ArrayList<TwoLevel_Bean> twoLevel_beens = new ArrayList<>();

            if(null != startMin)
            {
                TwoLevel_Bean two = new TwoLevel_Bean();
                two.setName(startMin);
                twoLevel_beens.add(two);
            }else
            {

                TwoLevel_Bean two = new TwoLevel_Bean();
                two.setName("00");
                TwoLevel_Bean two1 = new TwoLevel_Bean();
                two1.setName("30");
                twoLevel_beens.add(two);
                twoLevel_beens.add(two1);

            }
            new PickerView.Builder(context)
                    .setData(oneLevel_beens,twoLevel_beens)

                    .style(new PickerStyle().getDefaultStyle())
                    .listener(listener)
                    .build()
                    .show();

        }

        public static OptionPicker showDefaulStyleSingleSelectPicker(String[] datas, OptionPicker.OnOptionPickListener listener) {
            OptionPicker picker = new OptionPicker(AppManager.getCurrentActivity(), datas);
            picker.setSelectedIndex(0);
            picker.setTextSize(22);
            picker = setDefaultStyle(picker);
            picker.setOnOptionPickListener(listener);
            return picker;
        }

        public static OptionPicker showDefaulStyleSingleSelectPicker(String title,String[] datas, OptionPicker.OnOptionPickListener listener) {
            OptionPicker picker = new OptionPicker(AppManager.getCurrentActivity(), datas);
            picker.setSelectedIndex(0);
            picker.setTextSize(22);
            picker.setTitleText(title);
            picker = setDefaultStyle(picker);
            picker.setOnOptionPickListener(listener);
            return picker;
        }

        public static DoublePicker showDoubleStylePicker(List<String> list1, List<String> list2, DoublePicker.OnPickListener listener){
            DoublePicker picker = new DoublePicker(AppManager.getCurrentActivity(), list1,list2);
            picker.setSelectedIndex(0,0);
            picker.setTextSize(22);
            picker = setDefaultStyle(picker);
            picker.setOnPickListener(listener);
            return picker;
        }

        public static AddressPicker showDefaulStyleAddressPicker(AddressPicker.OnAddressPickListener lis, ArrayList<Province> data)
        {
            AddressPicker picker = new AddressPicker(AppManager.getCurrentActivity(), data);

            picker.setHideProvince(false);
            picker = setDefaultStyle(picker);
            picker.setOnAddressPickListener(lis);
            return picker;
        }

        private static <T extends WheelPicker>T setDefaultStyle(T picker)
        {
            picker.setTextSize(14);
            picker.setPadding(16);
            picker.setTopBackgroundColor(Utils.Resource.getColor(R.color.default_blue));
            picker.setBackgroundColor(Utils.Resource.getColor(R.color.white));
            picker.setTextColor(Utils.Resource.getColor(R.color.default_blue),Utils.Resource.getColor(R.color.text_gray_9) );
            picker.setLabelTextColor(Utils.Resource.getColor(R.color.text_default));
            picker.setSubmitTextColor(Utils.Resource.getColor(R.color.white));
            picker.setTopLineColor(Utils.Resource.getColor(R.color.line_e5e5e5));
            picker.setDividerColor(Utils.Resource.getColor(R.color.line_e5e5e5));
            picker.setCancelTextColor(Utils.Resource.getColor(R.color.white));
            picker.setPressedTextColor(Utils.Resource.getColor(R.color.text_default));
            return picker;
        }



    }


    /**
     * 手机号校验 注：1.支持最新145、147、166、198、199手机号码 2.支持+86校验
     *
     * @param phoneNum 手机号码
     * @return 验证通过返回true
     */
    public static boolean isMobile(String phoneNum) {
        if (phoneNum == null) {
            return false;
        }
        // 如果手机中有+86则会自动替换掉

        String telRegex = "^1(3[0-9]|4[57]|5[0-35-9]|6[6]|8[0-9]|9[89]|7[03678])\\d{8}$";
        return validation(telRegex, phoneNum.replace("+86", ""));
    }

}
